# coding:utf-8
import pymongo
import MongoOper
import RedisOper
import fralog.FraLog
from exceptions.fra_exception import FraException
from fralog.FraLog import getFileLog

# 数据库类型
TYPE_MONGO = 1
TYPE_REDIS = 2
TYPE_MYSQL = 3

DB_NAME = {
    TYPE_MONGO: 'mongo',
    TYPE_MYSQL: 'mysql',
    TYPE_REDIS: 'redis'
}
log = getFileLog()


class DBProxy(object):
    """
    数据存储层接口
    """
    # 默认使用mongo
    _type = TYPE_MONGO

    def __init__(self, dbtype=TYPE_MONGO, db=None):
        """
        :param dbtype: 数据库类型 
        :param db:  数据库连接实例
        """
        self._type = dbtype
        log.debug('初始化DBProxy，使用数据库: %s' % (DB_NAME[self._type]))
        if self._type == TYPE_MONGO or self._type == TYPE_REDIS:
            # self._dbclient = pymongo.MongoClient(host= host, port= port)
            # self._db = self._dbclient[dbname]
            self._db = db
        else:
            raise FraException('不支持的数据库类型')

    def _get_db_type(self):
        if self._db is None:
            # log.error('未指定数据库连接，该接口无法正常使用')
            raise FraException('DB not specified')
        else:
            if self._type > TYPE_REDIS:
                # log.error('目前还不支持: %s' % (DB_NAME[self._type]))
                raise FraException('not supported database')
            return self._type

    def get_db(self):
        if self._db is None:
            raise FraException('DB is None')
        else:
            return self._db

    def page_query(self, table, query=None, sort=None, pagesize=500, page=1):
        """
        数据查询
        :param query: 查询条件
        :return: 
        """
        if self._type == TYPE_MONGO:
            # log.debug('分页查询')
            ret = MongoOper.pagequery(mongo=self._db, table=table, query=query, sort=sort, pagesize=pagesize, page=page)
            # log.debug('查询结果返回')
            return ret
        else:
            raise FraException('不支持的数据库类型')

    def query(self, table, query=None):
        '''
        
        :param table: 
        :param query: 
        :return: 
        '''
        if self._get_db_type() == TYPE_MONGO:
            return MongoOper.find_one(self._db, table=table, query=query)
        else:
            raise FraException('不支持的数据库类型')

    def query_one(self, table, query=None):
        """
        返回符合条件的第一条结果
        :param table: 
        :param query: 
        :return: 
        """
        if self._get_db_type() == TYPE_MONGO:
            return MongoOper.find_one(self._db, table=table, query=query)
        else:
            raise FraException('不支持的数据库类型')

    def query_lastone(self, table, field):
        """
        返回符合条件的第一条结果
        :param table:
        :param query:
        :return:
        """
        if self._get_db_type() == TYPE_MONGO:
            return MongoOper.find_last(self._db, table=table, field=field)
        else:
            raise FraException('不支持的数据库类型')

    def insert(self, table, value):
        if self._get_db_type() == TYPE_MONGO:
            log.debug('插入数据')
            return MongoOper.insert(self._db, table=table, docs=value)
        else:
            raise FraException('不支持的数据库类型')

    def update(self, table, query, setvalue, insert_not_found=False):
        if self._get_db_type() == TYPE_MONGO:
            # log.debug('更新数据')
            return MongoOper.update(mongo=self._db, table=table, query=query, setdoc={'$set': setvalue},
                                    upsert=insert_not_found)
        else:
            raise FraException('不支持的数据库类型')

    def delete(self, table, query):
        if self._get_db_type() == TYPE_MONGO:
            # log.debug('删除数据')
            return MongoOper.delete(mongo=self._db, table=table, query=query)
        else:
            raise FraException('不支持的数据库类型')

    def distinct(self, table, field, query={}, options={}):
        if self._get_db_type() == TYPE_MONGO:
            # log.debug('删除数据')
            return MongoOper.distinct(mongo=self._db, table=table, field=field, query=query)
        else:
            raise FraException('不支持的数据库类型')

    def aggregate(self, table, aggreatelist):
        if self._get_db_type() == TYPE_MONGO:
            return MongoOper.aggregate(mongo=self._db, table=table, aggreatelist=aggreatelist)
        else:
            raise FraException('不支持的数据库类型')

    def distinct2field(self, table, field1, field2, query={}, options={}):
        if self._get_db_type() == TYPE_MONGO:
            # log.debug('删除数据')
            return MongoOper.distinct2field(mongo=self._db, table=table, field1=field1, field2=field2, query=query)
        else:
            raise FraException('不支持的数据库类型')


if __name__ == '__main__':
    dp = DBProxy()
    dp.query()
